import os
from string import Template

root  = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
project = os.path.basename(root)
print("project name: "+project)
serviceRoot = project+"/core/service"
daoRoot = project+"/core/dao"
tablePackage = project+"/core/dao/table"
commonPackage = project+"/core/service/common"
localwrapPackage  = project+"/core/localwrap"

packages = {
	"users":{
		"Users":{
			"daoPackage":"userdao",
			"dao":"Users",
			"table":"User"
		}
	},
	"graphs":{
		"Graphs":{
			"daoPackage":"graphdao",
			"dao":"Graphs",
			"table":"Graph"
		},
		"GraphElements":{
			"daoPackage":"graphdao",
			"dao":"GraphElements",
			"table":"GraphElement"
		},
		"GraphUsers":{
			"daoPackage":"graphdao",
			"dao":"GraphUsers",
			"table":"GraphUser"
		},
		"GraphElementDatas":{
			"daoPackage":"graphdao",
			"dao":"GraphElementDatas",
			"table":"GraphElementData"
		},
		"GraphElementProtoClass":{
			"daoPackage":"graphdao",
			"dao":"GraphElementProtoClasss",
			"table":"GraphElementProtoClass"
		}
	},
}

serviceTpl = '''package ${package}

import (
	"${daoRoot}/${daoPackage}"
	"${tablePackage}"
	"${localwrapPackage}"
)

type ${dao} struct{}

func (s ${dao}) Query(param ${daoPackage}.${dao}QueryParam) ([]table.${table}, int64) {
	ds := localwrap.GetRedisedMysql()
	defer ds.Close()
	return ${daoPackage}.${dao}{RedisedMysql: ds}.Query(param)
}
func (s ${dao}) Get(id int) table.${table} {
	ds := localwrap.GetRedisedMysql()
	defer ds.Close()
	return ${daoPackage}.${dao}{RedisedMysql: ds}.Get(id)
}
func (s ${dao}) Add(param ${daoPackage}.${dao}AddParam) table.${table} {
	ds := localwrap.GetRedisedMysql()
	defer ds.Close()
	return ${daoPackage}.${dao}{RedisedMysql: ds}.Add(param)
}
func (s ${dao}) Delete(id int) {
	ds := localwrap.GetRedisedMysql()
	defer ds.Close()
	${daoPackage}.${dao}{RedisedMysql: ds}.Delete(id)
}
func (s ${dao}) Update(param ${daoPackage}.${dao}UpdateParam) {
	ds := localwrap.GetRedisedMysql()
	defer ds.Close()
	${daoPackage}.${dao}{RedisedMysql: ds}.Update(param)
}


'''
serviceTestTpl='''package ${package}_test

import (
	"${daoRoot}/${daoPackage}"
	"${serviceRoot}/${package}"
	"testing"

	"github.com/stretchr/testify/suite"
)

func Test${dao}Suite(t *testing.T) {
	suite.Run(t, new(${dao}Suite))
}

type ${dao}Suite struct {
	suite.Suite
	x ${package}.${dao}
}

func (s *${dao}Suite) SetupSuite() {
}
func (s *${dao}Suite) SetupTest() {
}
func (s *${dao}Suite) TearDownTest() {
}
func (s *${dao}Suite) Test${dao}Main() {
	var addParam ${daoPackage}.${dao}AddParam
	addParam.Name = "testMain"
	newObject := s.x.Add(addParam)
	getObject := s.x.Get(newObject.Id)
	s.Equal(getObject.Id, newObject.Id)
	s.Equal(getObject.Name, addParam.Name)
	var updateParam ${daoPackage}.${dao}UpdateParam
	updateParam.Id = newObject.Id
	updateParam.Name = "testMainUpdate"
	s.x.Update(updateParam)
	getObject2 := s.x.Get(newObject.Id)
	s.Equal(updateParam.Name, getObject2.Name)
	s.x.Delete(newObject.Id)
}

'''



def write(content , package, file) :
	d = os.path.join(os.path.dirname(root),serviceRoot,package)
	if not os.path.exists(d) :
		os.makedirs(d)
	dst = os.path.join(d,file)
	if os.path.exists(dst) :
		print(dst +" has already exists,ignore it")
		return
	print("create "+dst)
	f = open(dst,"w+")
	f.write(content)
	f.close()

def make():
	tpl = Template(serviceTpl)
	testTpl = Template(serviceTestTpl)
	for package,services in packages.items():
		for name,service in services.items():
			param = {"package":package,"service":name,"dao":service['dao'],"table":service['table'],'daoPackage':service['daoPackage'],"serviceRoot":serviceRoot,"daoRoot":daoRoot,"tablePackage":tablePackage,"commonPackage":commonPackage,"localwrapPackage":localwrapPackage}
			service=tpl.substitute(param)
			write(service, package , name+".go")
			serviceTest=testTpl.substitute(param)
			write(serviceTest, package , name+"_test.go")
			

make()